<template>
  <div
    class="m-wangEditor"
    :class="{
      'focus-mode': focusMode,
      fullscreen: isFullscreen
    }"
  >
    <toolbar
      v-show="!focusMode"
      style="border-bottom: 1px solid #ccc"
      :editor="editorRef"
      :default-config="toolbarConfig"
      :mode="mode"
    />
    <editor
      v-model="valueHtml"
      class="editor-content"
      :default-config="editorConfig"
      :mode="mode"
      @on-created="handleCreated"
      @on-change="handleChange"
      @on-destroyed="handleDestroyed"
      @on-focus="handleFocus"
      @on-blur="handleBlur"
      @custom-alert="customAlert"
      @custom-paste="handlePaste"
    />
  </div>
</template>
<script lang="ts" setup>
// 引入 wangEditor
import { Editor, Toolbar } from '@wangeditor/editor-for-vue';
import '@wangeditor/editor/dist/css/style.css'; // 引入 css
import { computed, onBeforeUnmount, ref, shallowRef, watch } from 'vue';
import { IEditorConfig } from '@wangeditor/editor';
import { ElMessage } from 'element-plus';

// 组件属性和事件
interface Props {
  modelValue?: string;
  focusMode?: boolean;
  isFullscreen?: boolean;
  placeholder?: string;
}

interface Emits {
  (e: 'update:modelValue', value: string): void;
  (e: 'on-created', editor: Editor): void;
  (e: 'on-change', editor: Editor): void;
  (e: 'on-focus', editor: Editor): void;
  (e: 'on-blur', editor: Editor): void;
}

const props = withDefaults(defineProps<Props>(), {
  modelValue: '',
  focusMode: false,
  isFullscreen: false,
  placeholder: '开始你的创作...'
});

const emit = defineEmits<Emits>();

// 编辑器实例，必须用 shallowRef
const editorRef = shallowRef<Editor>();

// 记录上一次的内容，用于检测实际变化
const lastContent = ref<string>('');

// 编辑器配置
const toolbarConfig = {
  // 可以在这里自定义工具栏配置
  excludeKeys: [
    // 排除一些不需要的按钮
    'group-video',
    'insertTable',
    'todo'
  ]
};

const editorConfig: Partial<IEditorConfig> = {
  placeholder: props.placeholder,
  autoFocus: true,
  scroll: true,
  hoverbarKeys: {
    image: {
      menuKeys: ['editImage', 'viewImageLink', 'deleteImage']
    }
  },
  MENU_CONF: {
    uploadImage: {
      server: '/api/upload', // 图片上传地址
      maxFileSize: 5 * 1024 * 1024, // 5M
      maxNumberOfFiles: 10,
      allowedFileTypes: ['image/*'],
      metaWithUrl: true,
      withCredentials: true,
      timeout: 5 * 1000, // 5秒超时
      customInsert: (res: any, insertFn: Function) => {
        // 从 res 中获取图片 url
        const url = res.data?.url;
        if (url) {
          insertFn(url);
        } else {
          ElMessage.error('图片上传失败');
        }
      },
      onError: (file: File, err: any, res: any) => {
        ElMessage.error(`图片 ${file.name} 上传失败`);
      }
    }
  }
};

// 内容 HTML
const mode = ref('default');

// 计算属性
const valueHtml = computed({
  get() {
    return props.modelValue;
  },
  set(val) {
    // 防止富文本内容为空时，校验失败
    if (editorRef.value && editorRef.value.isEmpty()) val = '<p><br></p>';
    emit('update:modelValue', val);
  }
});

// 监听属性变化
watch(
  () => props.placeholder,
  newPlaceholder => {
    if (editorRef.value) {
      editorRef.value.getConfig().placeholder = newPlaceholder;
    }
  }
);

watch(
  () => props.focusMode,
  newFocusMode => {
    if (editorRef.value) {
      if (newFocusMode) {
        editorRef.value.blur();
      } else {
        editorRef.value.focus();
      }
    }
  }
);

// 编辑器事件处理
const handleCreated = (editor: Editor) => {
  editorRef.value = editor; // 记录 editor 实例，重要！
  // 初始化记录的内容
  lastContent.value = editor.getHtml();
  emit('on-created', editor);
};

const handleChange = (editor: Editor) => {
  // 获取当前内容
  const currentContent = editor.getHtml();

  // 只有当内容真正发生变化时才触发事件
  if (currentContent !== lastContent.value) {
    lastContent.value = currentContent;
    emit('on-change', editor);
  }
};

const handleDestroyed = (editor: Editor) => {
  console.log('destroyed', editor);
};

const handleFocus = (editor: Editor) => {
  emit('on-focus', editor);
};

const handleBlur = (editor: Editor) => {
  emit('on-blur', editor);
};

const customAlert = (info: string, type: string) => {
  // 移除alert，改用更友好的提示
  if (type === 'error') {
    ElMessage.error(info);
  } else if (type === 'success') {
    ElMessage.success(info);
  } else {
    ElMessage.info(info);
  }
};

// 增强粘贴处理
const handlePaste = (editor: Editor, event: ClipboardEvent, callback: Function) => {
  const items = event.clipboardData?.items;

  if (!items) {
    callback(true);
    return;
  }

  // 处理图片粘贴
  for (const item of items) {
    if (item.type.indexOf('image') !== -1) {
      const file = item.getAsFile();
      if (file) {
        // 这里可以调用图片上传API
        // const formData = new FormData();
        // formData.append('file', file);
        // uploadImage(formData).then(url => {
        //   editor.insertNode(createImageNode(url));
        // });
        event.preventDefault();
        callback(false);
        return;
      }
    }
  }

  // 处理纯文本粘贴
  const text = event.clipboardData?.getData('text/plain');
  if (text) {
    // 检查是否是Markdown格式
    if (isMarkdown(text)) {
      const html = markdownToHtml(text);
      editor.dangerouslyInsertHtml(html);
      event.preventDefault();
      callback(false);
      return;
    }
  }

  callback(true);
};

// 辅助函数：检查是否为Markdown格式
const isMarkdown = (text: string): boolean => {
  const markdownPatterns = [
    /^#{1,6}\s+/, // 标题
    /^\*{1,2}[^*]+\*{1,2}$/, // 加粗/斜体
    /^\[[^\]]+\]\([^)]+\)$/, // 链接
    /^`[^`]+`$/, // 行内代码
    /^```[\s\S]*```$/, // 代码块
    /^[-+*]\s/, // 无序列表
    /^\d+\.\s/ // 有序列表
  ];

  return markdownPatterns.some(pattern => pattern.test(text));
};

// 辅助函数：Markdown转HTML（简化版）
const markdownToHtml = (markdown: string): string =>
  markdown
    .replace(/^#{1,6}\s+(.+)$/gm, '<h3>$1</h3>') // 简化：所有标题转为h3
    .replace(/\*\*(.+?)\*\*/g, '<strong>$1</strong>') // 加粗
    .replace(/\*(.+?)\*/g, '<em>$1</em>') // 斜体
    .replace(/`(.+?)`/g, '<code>$1</code>') // 行内代码
    .replace(/\n/g, '<br>'); // 换行
// 组件销毁时，也及时销毁编辑器
onBeforeUnmount(() => {
  const editor = editorRef.value;
  if (editor == null) {
    return;
  }
  editor.destroy();
});

// 暴露给父组件的方法
defineExpose({
  editorRef,
  getEditor: () => editorRef.value,
  getContent: () => editorRef.value?.getHtml() || '',
  setContent: (content: string) => {
    if (editorRef.value) {
      editorRef.value.setHtml(content);
      // 更新记录的内容，避免下次change事件误触发
      lastContent.value = content;
    }
  },
  focus: () => {
    if (editorRef.value) {
      editorRef.value.focus();
    }
  },
  blur: () => {
    if (editorRef.value) {
      editorRef.value.blur();
    }
  }
});
</script>
<style lang="scss" scoped>
.m-wangEditor {
  z-index: 99;
  width: 100%;
  height: 100%;
  border: 1px solid #cccccc;
  border-radius: 8px;
  overflow: hidden;
  transition: all 0.3s ease;

  // 专注模式
  &.focus-mode {
    border: none;
    border-radius: 0;
    background: #fafafa;

    .editor-content {
      max-width: 800px;
      background: white;
      height: calc(100vh - 50px);
      box-shadow: 0 0 20px rgba(0, 0, 0, 0.1);
    }

    :deep(.w-e-text-container) {
      background: white;
    }

    :deep(.w-e-toolbar) {
      display: none;
    }
  }

  // 全屏模式
  &.fullscreen {
    position: fixed;
    top: 0;
    left: 0;
    width: 100vw;
    height: 100vh;
    z-index: 9999;
    border: none;
    border-radius: 0;
    background: white;

    .editor-content {
      height: calc(100vh - 50px);
    }
  }

  .editor-toolbar {
    border-bottom: 1px solid #cccccc;
  }

  .editor-content {
    height: 100%;
    min-height: 300px; /* 设置最小高度 */
    overflow-y: auto;

    :deep(.w-e-text-container) {
      min-height: 250px; /* 文本容器最小高度 */
      height: auto; /* 允许高度自适应 */
      max-height: 100%; /* 最大高度不超过容器 */
      padding: 0px;
      padding-bottom: 20px; /* 添加底部内边距，确保内容不被遮挡 */
      font-size: 16px;
      line-height: 1.6;
      overflow-y: auto; /* 确保文本容器可以滚动 */

      // 专注模式下的文本样式
      .focus-mode & {
        font-family: 'Georgia', serif;
        font-size: 18px;
        color: #333;
        padding: 40px;
        padding-bottom: 60px; /* 专注模式下增加更多底部空间 */
      }
    }

    // 编辑器占位符样式
    :deep(.w-e-text-placeholder) {
      font-size: 16px;
      color: #999;
      user-select: none;
    }

    // 编辑器滚动条样式
    :deep(.w-e-text-container)::-webkit-scrollbar {
      width: 8px;
    }

    :deep(.w-e-text-container)::-webkit-scrollbar-track {
      background: #f1f1f1;
    }

    :deep(.w-e-text-container)::-webkit-scrollbar-thumb {
      background: #888;
      border-radius: 4px;
    }

    :deep(.w-e-text-container)::-webkit-scrollbar-thumb:hover {
      background: #555;
    }
  }

  // 工具栏样式优化
  :deep(.w-e-toolbar) {
    border-radius: 8px 8px 0 0;
    padding: 8px;
    background: #f8f9fa;
    position: relative;
    z-index: 1000; /* 确保工具栏层级更高 */
  }

  // 工具栏下拉菜单样式 - 修复被遮挡问题
  :deep(.w-e-toolbar .w-e-menu-tooltip) {
    z-index: 1001 !important; /* 下拉提示框层级最高 */
  }

  // WangEditor 下拉菜单层级修复
  :deep(.w-e-toolbar .w-e-select-list) {
    z-index: 1002 !important; /* 下拉列表层级最高 */
    position: absolute;
  }

  // 所有弹出菜单的层级设置
  :deep(.w-e-bar-dialog) {
    z-index: 1003 !important; /* 对话框层级最高 */
  }

  // 编辑器内容区域层级设置 - 确保不会遮挡工具栏下拉菜单
  :deep(.w-e-text-container) {
    position: relative;
    z-index: 1; /* 内容区域层级较低 */
  }

  // 代码块样式
  :deep(.w-e-text pre) {
    background: #f4f4f4;
    border: 1px solid #ddd;
    border-radius: 4px;
    padding: 16px;
    overflow-x: auto;
    font-family: 'Monaco', 'Menlo', monospace;
    font-size: 14px;
  }

  // 引用样式
  :deep(.w-e-text blockquote) {
    border-left: 4px solid #ddd;
    padding-left: 16px;
    margin: 16px 0;
    color: #666;
    font-style: italic;
  }

  // 标题样式
  :deep(.w-e-text h1),
  :deep(.w-e-text h2),
  :deep(.w-e-text h3),
  :deep(.w-e-text h4),
  :deep(.w-e-text h5),
  :deep(.w-e-text h6) {
    margin: 24px 0 16px;
    font-weight: 600;
    line-height: 1.25;
  }

  :deep(.w-e-text h1) {
    font-size: 2em;
  }
  :deep(.w-e-text h2) {
    font-size: 1.5em;
  }
  :deep(.w-e-text h3) {
    font-size: 1.25em;
  }
  :deep(.w-e-text h4) {
    font-size: 1em;
  }

  // 段落样式
  :deep(.w-e-text p) {
    margin: 16px 0;
    line-height: 1.6;
  }

  // 链接样式
  :deep(.w-e-text a) {
    color: #1890ff;
    text-decoration: none;
    transition: color 0.3s;

    &:hover {
      color: #40a9ff;
      text-decoration: underline;
    }
  }

  // 列表样式
  :deep(.w-e-text ul),
  :deep(.w-e-text ol) {
    padding-left: 24px;
    margin: 16px 0;
  }

  :deep(.w-e-text li) {
    margin: 8px 0;
    line-height: 1.6;
  }

  // 图片样式
  :deep(.w-e-text img) {
    max-width: 100%;
    height: auto;
    border-radius: 4px;
    margin: 16px 0;
    box-shadow: 0 2px 8px rgba(0, 0, 0, 0.1);
  }

  // 表格样式
  :deep(.w-e-text table) {
    width: 100%;
    border-collapse: collapse;
    margin: 16px 0;
    border-radius: 4px;
    overflow: hidden;
    box-shadow: 0 1px 3px rgba(0, 0, 0, 0.1);
  }

  :deep(.w-e-text th),
  :deep(.w-e-text td) {
    border: 1px solid #e8e8e8;
    padding: 12px;
    text-align: left;
  }

  :deep(.w-e-text th) {
    background: #fafafa;
    font-weight: 600;
  }

  :deep(.w-e-text tr:nth-child(even)) {
    background: #fafafa;
  }
}
</style>
